package forum.server.persistence;

import forum.server.domain.Gender;
import forum.server.domain.LoggedInUser;
import forum.server.domain.Post;
import forum.server.domain.PostContent;
import java.util.Date;
import java.util.Vector;
import org.junit.After;
import org.junit.AfterClass;
import org.junit.Before;
import org.junit.BeforeClass;
import org.junit.Test;
import static org.junit.Assert.*;
public class DataManipulatorTest {

    public DataManipulatorTest() {
    }

    @BeforeClass
    public static void setUpClass() throws Exception {

    }

    @AfterClass
    public static void tearDownClass() throws Exception {

    }
    @Before
    public void setUp() {
        try{
            DataManipulatorProxy.getInstance().resetDataBase();
        }
        catch (Exception e) {        	
            e.printStackTrace();
        }
    }

    @After
    public void tearDown() {
    }



    /**
     * Test of resetDataBase method, of class DataManipulator.
     */
    @Test
    public void testResetDataBase() {
        System.out.println("resetDataBase");
        try{
            DataManipulatorInt instance = DataManipulatorProxy.getInstance();
            instance.resetDataBase();
            assertTrue(instance.getPosts().size()==0);
            assertTrue(instance.countUsers()==1);
        }
        catch (Exception e){
        	e.printStackTrace();
        	fail("test failed threw an exception");
        }
    }

    /**
     * Test of getReplies method, of class DataManipulator.
     */
    @Test
    public void testGetReplies() {
        System.out.println("getReplies");
        try{
            int postId = DataManipulatorProxy.getInstance().generateNewPostId();
            DataManipulatorInt instance = DataManipulatorProxy.getInstance();
            Date now=new Date();
            
            PostContent pc=new PostContent("hello world");
            Post p = new Post("teamBannna","this is the bannana forum",pc,postId,-1,now, now);
            instance.addPost(p);
            now=new Date();
            pc=new PostContent("testing reply");
            Post reply1 = new Post("teamBannna tests","testing reply",pc,instance.generateNewPostId(),postId,now,now);
            now=new Date();
            pc=new PostContent("testing reply2");
            Post reply2 = new Post("teamBannna tests2","testing reply2",pc,instance.generateNewPostId(),postId,now,now);
            instance.addReply(postId, reply1);
            instance.addReply(postId, reply2);
            int expResult = 2;
            Vector<Post> result = instance.getReplies(postId);
            assertEquals(expResult, result.size());
        }
        catch (Exception e){
        	e.printStackTrace();
        	fail("test failed threw an exception");
        }
       
    }

    /**
     * Test of getPosts method, of class DataManipulator.
     */
    @Test
    public void testGetPosts() {
        System.out.println("getPosts");
        try{
            int postId = 1;
            DataManipulatorInt instance = DataManipulatorProxy.getInstance();
            Date now=new Date();
            PostContent pc=new PostContent("hello world");
            Post p = new Post("teamBannna","this is the bannana forum",
                    pc,instance.generateNewPostId(),-1,now, now);
            instance.addPost(p);
            now=new Date();
            pc=new PostContent("testing reply");
            Post reply1 = new Post("teamBannna tests","testing reply",
                    pc,instance.generateNewPostId(),1,now,now);

            now=new Date();
            pc=new PostContent("testing reply2");
            Post reply2 = new Post("teamBannna tests2","testing reply2",
                    pc,instance.generateNewPostId(),1,now,now);

            instance.addReply(postId, reply1);
            instance.addReply(postId, reply2);
            Post p2 = new Post("teamBannna tests2","testing reply2",
                    pc,instance.generateNewPostId(),1,now,now);

            instance.addPost(p2);
            int expResult = 2;
            Vector<Post> result = instance.getPosts();
            assertEquals(expResult, result.size());
        }
        catch (Exception e){
        	e.printStackTrace();
        	fail("test failed threw an exception");
        }
    }

    /**
     * Test of deletePost method, of class DataManipulator.
     */
    @Test
    public void testDeletePost() {
        System.out.println("deletePost");
        try{
            DataManipulatorInt instance = DataManipulatorProxy.getInstance();
            Date now=new Date();
            PostContent pc=new PostContent("hello world");
            Post p = new Post("teamBannna","this is the bannana forum",
                    pc,instance.generateNewPostId(),-1,now, now);

            now=new Date();
            pc=new PostContent("testing reply");
            Post reply1 = new Post("teamBannna tests","testing reply",
                    pc,instance.generateNewPostId(),1,now,now);

            now=new Date();
            pc=new PostContent("testing reply2");
            Post reply2 = new Post("teamBannna tests2","testing reply2",
                    pc,instance.generateNewPostId(),1,now,now);


            Post p2 = new Post("teamBannna tests2","testing reply2",
                    pc,instance.generateNewPostId(),-1,now,now);

            instance.addPost(p);
            instance.addReply(p.getPostId(), reply1);
            instance.addPost(p2);
            instance.addReply(p2.getPostId(), reply2);
            System.out.println(reply2.getParentId()+"  "+reply2.getPostId());
            assertTrue(instance.getPosts().size()==2);
            assertTrue(instance.getReplies(p2.getPostId()).size()==1);
            instance.deletePost(p2.getPostId());
            assertTrue(instance.getPosts().size()==1);
        }
        catch (Exception e){
        	e.printStackTrace();
        	fail("test failed threw an exception");
        }
    }

    /**
     * Test of deleteUser method, of class DataManipulator.
     */
    @Test
    public void testDeleteUser() {
        System.out.println("deleteUser");
        try{
            DataManipulatorInt instance = DataManipulatorProxy.getInstance();
            LoggedInUser user = new LoggedInUser("new logged", "123456", "newUser",
                    "newUser", "myEmail", Gender.MALE, "NY", new Date());
            instance.addUser(user);
            instance.deleteUser("new logged");
            assertTrue(instance.countUsers()==1);
        }
        catch (Exception e){
        	e.printStackTrace();
        	fail("test failed threw an exception");
        }
    }

    /**
     * Test of addUser method, of class DataManipulator.
     */
    @Test
    public void testAddUser() {
        System.out.println("addUser");
        LoggedInUser user = new LoggedInUser("new logged", "123456", "newUser",
                "newUser", "myEmail", Gender.MALE, "NY", new Date());
        try{
            DataManipulatorInt instance = DataManipulatorProxy.getInstance();
            instance.addUser(user);
            assertTrue(instance.isUserExists(user.getUsername()));
        }
        catch (Exception e){
        	e.printStackTrace();
        	fail("test failed threw an exception");
        }
    }

    /**
     * Test of doesUserExists method, of class DataManipulatorInt.
     */
    @Test
    public void testDoesUserExists() {
        System.out.println("doesUserExists");
        LoggedInUser user = new LoggedInUser("new logged", "123456", "newUser",
                "newUser", "myEmail", Gender.MALE, "NY", new Date());
        try{
            DataManipulatorInt instance = DataManipulatorProxy.getInstance();
            instance.addUser(user);
            assertTrue(instance.isUserExists(user.getUsername()));
        }
        catch (Exception e){
        	e.printStackTrace();
        	fail("test failed threw an exception");
        }
    }

    /**
     * Test of countUsers method, of class DataManipulatorInt.
     */
    @Test
    public void testCountUsers() {
        System.out.println("countUsers");
        LoggedInUser user = new LoggedInUser("new logged", "123456", "newUser",
                "newUser", "myEmail", Gender.MALE, "NY", new Date());
        try{
            DataManipulatorInt instance = DataManipulatorProxy.getInstance();
            instance.addUser(user);
            LoggedInUser user2 = new LoggedInUser("new logged2", "123456", "newUser",
                    "newUser", "myEmail", Gender.MALE, "NY", new Date());
            instance.addUser(user2);
            int expResult = 3;
            int result = instance.countUsers();
            assertEquals(expResult, result);
        }
        catch (Exception e){
        	e.printStackTrace();
        	fail("test failed threw an exception");
        }
        
    }

    /**
     * Test of addReply method, of class DataManipulatorInt.
     */
    @Test
    public void testAddReply() {
        System.out.println("addReply");
        try{
            DataManipulatorInt instance = DataManipulatorProxy.getInstance();
            Date now=new Date();
            PostContent pc=new PostContent("hello world");
            Post p = new Post("teamBannna","this is the bannana forum",
                    pc,instance.generateNewPostId(),-1,now, now);
            int fatherId = p.getPostId();
            instance.addPost(p);
            pc=new PostContent("testing reply");
            Post reply = new Post("teamBannna tests","testing reply",
                    pc,instance.generateNewPostId(),fatherId,now,now);
            instance.addReply(fatherId, reply);
            assertTrue(instance.getPosts().size()!=0);
            assertTrue(instance.getPost(reply.getPostId()).getAuthor().equals("teamBannna tests"));
            assertTrue(instance.getPost(reply.getPostId()).getHeader().equals("testing reply"));
            assertTrue(instance.getPost(reply.getPostId()).getContent().getContent().equals("testing reply"));
        }
        catch (Exception e){
        	e.printStackTrace();
        	fail("test failed threw an exception");
        }
    }

    /**
     * Test of addPost method, of class DataManipulatorInt.
     */
    @Test
    public void testAddPost() {
        System.out.println("addPost");
        try{
            DataManipulatorInt instance = DataManipulatorProxy.getInstance();
            Date now=new Date();
            PostContent pc=new PostContent("hello world");
            Post p = new Post("teamBannna","this is the bannana forum",
                    pc,instance.generateNewPostId(),-1,now, now);

            instance.addPost(p);
            assertTrue(instance.getPosts().size()!=0);
            assertTrue(instance.getPost(p.getPostId()).getAuthor().equals("teamBannna"));
            assertTrue(instance.getPost(p.getPostId()).getHeader().equals("this is the bannana forum"));
            assertTrue(instance.getPost(p.getPostId()).getContent().getContent().equals("hello world"));
        }
        catch (Exception e){
        	e.printStackTrace();
        	fail("test failed threw an exception");
        }
    }

    /**
     * Test of modifyPost method, of class DataManipulatorInt.
     */
    @Test
    public void testModifyPost() {
        System.out.println("modifyPost");
        try{
            DataManipulatorInt instance = DataManipulatorProxy.getInstance();
            Date now=new Date();
            PostContent pc=new PostContent("hello world1");
            Post p = new Post("teamBannna","this is the bannana forum",
                    pc,instance.generateNewPostId(),-1,now, now);
            instance.addPost(p);
            int postId = p.getPostId();
            pc=new PostContent("just hell");
            instance.modifyPost(postId, pc);
            assertTrue(instance.getPost(postId).getContent().getContent().equals("just hell"));
        }
        catch (Exception e){
        	e.printStackTrace();
        	fail("test failed threw an exception");
        }
    }

    /**
     * Test of getPost method, of class DataManipulatorInt.
     */
    @Test
    public void testGetPost() {
        System.out.println("getPost");
        try{
            DataManipulatorInt instance = DataManipulatorProxy.getInstance();
            Date now=new Date();
            PostContent pc=new PostContent("hello world1");
            Post p = new Post("teamBannna","this is the bannana forum",
                    pc,instance.generateNewPostId(),-1,now, now);
            instance.addPost(p);
            int postId = p.getPostId();
            pc=new PostContent("just hell");
            instance.modifyPost(postId, pc);
            assertTrue(instance.getPost(postId)!=null);
        }
        catch (Exception e){
        	e.printStackTrace();
        	fail("test failed threw an exception");
        }
    }

    /**
     * Test of getUser method, of class DataManipulatorInt.
     */
    @Test
    public void testGetUser() {
        System.out.println("getUser");
        try{
            DataManipulatorInt instance = DataManipulatorProxy.getInstance();
            LoggedInUser user = new LoggedInUser("new logged", "123456", "newUser",
                    "newUser", "myEmail", Gender.MALE, "NY", new Date());
            instance.addUser(user);
            assertTrue(instance.getUser("new logged").getCity().equals("NY"));
        }
        catch (Exception e){
            e.printStackTrace();
            fail("test failed threw an exception");
        }
    }
}